#!/usr/bin/env python3
"""
基于发现的字符表尝试高级解密
"""

import base64
from collections import Counter

def load_encrypted_data():
    """加载加密数据"""
    with open('encript_body.txt', 'r') as f:
        return f.read().strip()

def load_decoded_binary():
    """加载Base64解码后的二进制数据"""
    with open('decoded_result.bin', 'rb') as f:
        return f.read()

def try_reverse_engineering_approach():
    """尝试逆向工程方法"""
    print("🔍 === 基于逆向工程的解密尝试 ===\n")
    
    # 从二进制中找到的字符序列
    found_charset = "!#$&'()*+,-./0123456789:;=?@ABCDEFGHIJKLMNOPQRSTUVWXYZ_abcdefghijklmnopqrstuvwxyz~"
    
    # 我们的加密数据使用的字符集
    our_charset_chars = sorted(set(load_encrypted_data()))
    our_charset = ''.join(our_charset_chars)
    
    print(f"发现的字符集 ({len(found_charset)}个): {found_charset}")
    print(f"我们的字符集 ({len(our_charset)}个): {our_charset}")
    
    # 标准Base64字符集
    std_base64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
    
    # 尝试创建映射
    print("\n尝试映射方案1: 按位置映射")
    if len(our_charset) == 64:
        mapping1 = {}
        for i, char in enumerate(our_charset):
            if i < len(std_base64):
                mapping1[char] = std_base64[i]
        
        # 尝试解密
        encrypted_data = load_encrypted_data()
        translated = ''.join(mapping1.get(c, c) for c in encrypted_data)
        
        try:
            # 添加padding
            padding = (4 - len(translated) % 4) % 4
            translated += '=' * padding
            
            decoded = base64.b64decode(translated)
            print(f"解码成功! 长度: {len(decoded)}")
            
            # 分析解码结果
            analyze_decoded_data(decoded)
            
            # 尝试进一步解密
            try_further_decryption(decoded)
            
        except Exception as e:
            print(f"解码失败: {e}")

def analyze_decoded_data(data):
    """分析解码后的数据"""
    print("\n📊 === 分析解码数据 ===")
    
    # 字节分布
    byte_freq = Counter(data)
    most_common = byte_freq.most_common(10)
    
    print(f"数据长度: {len(data)} 字节")
    print("最常见的字节:")
    for byte_val, count in most_common:
        char_repr = chr(byte_val) if 32 <= byte_val <= 126 else f'\\x{byte_val:02x}'
        print(f"  0x{byte_val:02x} ({char_repr}): {count}次")
    
    # 检查是否有可读文本
    printable_chars = sum(1 for b in data if 32 <= b <= 126)
    print(f"\n可打印字符: {printable_chars}/{len(data)} ({printable_chars/len(data)*100:.1f}%)")

def try_further_decryption(decoded_data):
    """尝试进一步解密"""
    print("\n🔐 === 尝试进一步解密 ===")
    
    # 1. 基于频率分析的字节替换
    print("\n1. 基于频率分析:")
    
    # JSON的预期字符频率（大致）
    json_common_chars = ' ",:{}[]'
    json_common_bytes = [ord(c) for c in json_common_chars]
    
    # 获取解码数据中最常见的字节
    byte_freq = Counter(decoded_data)
    most_common_bytes = [b for b, _ in byte_freq.most_common(len(json_common_bytes))]
    
    # 创建映射
    mapping = {}
    for i, freq_byte in enumerate(most_common_bytes):
        if i < len(json_common_bytes):
            mapping[freq_byte] = json_common_bytes[i]
    
    # 应用映射
    result = bytearray()
    for byte in decoded_data[:200]:
        result.append(mapping.get(byte, byte))
    
    print(f"映射结果预览: {bytes(result[:100])}")
    
    # 2. 已知明文攻击
    print("\n2. 已知明文攻击:")
    
    # 我们知道应该包含 "questionText"
    known_plaintext = b'"questionText"'
    
    # 在解码数据中寻找可能的位置
    for i in range(len(decoded_data) - len(known_plaintext) + 1):
        segment = decoded_data[i:i+len(known_plaintext)]
        
        # 计算XOR密钥
        xor_key = bytes(a ^ b for a, b in zip(segment, known_plaintext))
        
        # 检查密钥是否有规律
        if len(set(xor_key)) == 1:  # 单字节XOR
            key_byte = xor_key[0]
            print(f"\n  找到可能的单字节XOR: 0x{key_byte:02x} 在位置 {i}")
            
            # 解密
            decrypted = bytes(b ^ key_byte for b in decoded_data)
            
            # 检查是否包含JSON特征
            if b'{"' in decrypted[:100] or b'"questionText"' in decrypted:
                print("  ✅ 解密成功!")
                with open('final_decrypted.json', 'wb') as f:
                    f.write(decrypted)
                print("  结果已保存到 final_decrypted.json")
                print(f"  预览: {decrypted[:200]}")
                return decrypted
        
        elif len(set(xor_key[:4])) == 1 and len(set(xor_key[4:8])) == 1:
            # 可能是重复的密钥
            key_len = 4
            for kl in [2, 4, 8]:
                if all(xor_key[j] == xor_key[j % kl] for j in range(len(xor_key))):
                    print(f"\n  找到可能的{kl}字节循环XOR 在位置 {i}")
                    cycle_key = xor_key[:kl]
                    
                    # 解密前200字节测试
                    test_decrypt = bytes(decoded_data[j] ^ cycle_key[j % kl] for j in range(200))
                    if b'{"' in test_decrypt or b'"questionText"' in test_decrypt:
                        print(f"  可能的密钥: {cycle_key.hex()}")
                        print(f"  解密测试: {test_decrypt[:100]}")
    
    # 3. 字符旋转
    print("\n3. 尝试字符旋转:")
    
    # 尝试不同的旋转值
    for rot in [13, 47, 94]:  # ROT13, ROT47等
        result = bytearray()
        for byte in decoded_data[:100]:
            if 33 <= byte <= 126:  # 可打印ASCII范围
                rotated = ((byte - 33 + rot) % 94) + 33
                result.append(rotated)
            else:
                result.append(byte)
        
        # 检查结果
        if b'{"' in result or b'question' in result:
            print(f"\n  ROT{rot}可能有效: {bytes(result[:50])}")

def analyze_encryption_pattern():
    """分析加密模式"""
    print("\n\n🧩 === 分析加密模式 ===")
    
    encrypted = load_encrypted_data()
    decoded = load_decoded_binary()
    
    print(f"加密数据长度: {len(encrypted)}")
    print(f"解码数据长度: {len(decoded)}")
    print(f"压缩率: {len(decoded)/len(encrypted):.2f}")
    
    # 查找重复模式
    print("\n重复模式分析:")
    
    # 在加密数据中找重复
    for pattern_len in [8, 12, 16]:
        patterns = {}
        for i in range(len(encrypted) - pattern_len + 1):
            pattern = encrypted[i:i+pattern_len]
            if pattern not in patterns:
                patterns[pattern] = []
            patterns[pattern].append(i)
        
        repeated = [(p, pos) for p, pos in patterns.items() if len(pos) >= 3]
        if repeated:
            print(f"\n长度{pattern_len}的重复模式:")
            for pattern, positions in repeated[:3]:
                print(f"  '{pattern}': {len(positions)}次")
                
                # 检查对应的解码位置
                decoded_positions = [int(p * len(decoded) / len(encrypted)) for p in positions[:3]]
                print(f"    解码位置: {decoded_positions}")

if __name__ == "__main__":
    try_reverse_engineering_approach()
    analyze_encryption_pattern()
    
    print("\n\n💡 === 结论 ===")
    print("基于分析：")
    print("1. 使用了自定义的64字符Base64编码")
    print("2. Base64解码后还有额外的加密层")
    print("3. 可能的加密方式：")
    print("   - 单字节或多字节XOR")
    print("   - 字节替换表")
    print("   - 或两者的组合")
    print("\n下一步建议：")
    print("1. 通过动态调试捕获加密过程")
    print("2. 分析更多的请求样本找出规律")
    print("3. 尝试反编译相关的加密函数")